public class MrX extends Agent
{
	public MrX(Node positionIn, Map map)
	{
		super(positionIn, map);
		tickets[TAXI] = 4;
		tickets[BUS] = 3;
		tickets[UNDERGROUND] = 3;
		tickets[BLACK] = 5;
		tickets[TWO_TIMES] = 2;
	}

	private float ticketsValue(Node n)
	{
		float n_tickets = 0;
		for(Integer c : n.waysConnected(getPosition())) {
			int n_tmp = 0;
			switch (c) {
				case TAXI:
					n_tmp = tickets[TAXI];
					break;
				case BUS:
					n_tmp = tickets[BUS];
					break;
				case UNDERGROUND:
					n_tmp = tickets[UNDERGROUND];
					break;
				case BLACK:
					n_tmp = tickets[BLACK];
					break;
			}
			if (n_tmp > n_tickets) {
				n_tickets = n_tmp;
			}
		}
		return n_tickets;
	}

	private float connectionsValue(Node n)
	{
		float direct_connections = -1;
		float indirect_connections = -1;

		for(Node neighbour : n.connectedNodes()) {
			direct_connections++;
			for(Node neighbour2 : neighbour.connectedNodes()) {
				indirect_connections++;
			}
		}
		return direct_connections + indirect_connections / 3;
	}

	private float distanceValue(Node n, Node[] occupied)
	{
		for(Node o : occupied) {
			if (o == n) {
				return 0;
			}
		}
		for(Node neighbour : n.connectedNodes()) {
			for(Node o : occupied) {
				if (o == neighbour) {
					return (float) 0.01;
				}
			}
			for(Node neighbour2 : neighbour.connectedNodes()) {
				for(Node o : occupied) {
					if (o == neighbour2) {
						return (float) 0.2;
					}
				}
				for(Node neighbour3 : neighbour2.connectedNodes()) {
					for(Node o : occupied) {
						if (o == neighbour3) {
							return (float) 0.4;
						}
					}
				}
			}
		}
		return 1;
	}

	public void move()
	{
        System.out.printf("Calculating route from position: %d\n", position.getNum());
		Node[] positions = map.getAgentPositions();
		Node[] occupied = new Node[5];
		for (int i=0; i < 5; i++) {
			occupied[i] = positions[i];
		}

		/*  for each connection
		 *		if has tickets for traveling
		 *			value = n_tickets*n_connections*n_connection_types*distance_to_detective
		 *	take action with highest value
		 */

		Node bestNode = null;
		float bestVal = 0;
        System.out.println("before for");
		for(Node neighbour : getPosition().connectedNodes()) {
			float n_tickets = ticketsValue(neighbour);
			float n_connections = connectionsValue(neighbour);
			System.out.print("Starting distanceValue() ... ");
			float n_distance = distanceValue(neighbour, occupied);
			System.out.println("done");
			float val = n_tickets*n_connections*n_distance;
			if (val > bestVal) {
				bestNode = neighbour;
				bestVal = val;
			}
		}
		int type = 0;
		int num = 0;
		for(int connection_type : getPosition().waysConnected(bestNode)) {
			if (num < tickets[connection_type]) {
				num = tickets[connection_type];
				type = connection_type;
			}
		}
        System.out.printf("best node: %s, Type: %s\n", bestNode.getNum(), type);
		moveToPosition(new Movement(bestNode, type));
	}

	public void setDefaultVisibility()
	{
		visible = false;
	}
}
